package co.fitstart.entity.user;

import java.util.Date;
import java.util.LinkedHashMap;
import java.util.Map;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.persistence.Transient;

import com.fasterxml.jackson.annotation.JsonIgnoreProperties;

import co.fitstart.entity.reference.Gender;

/**
 * user wechat account
 * 
 * @author Leo
 */
@Entity
@Table(name = "wechat_account")
@JsonIgnoreProperties(value={"hibernate_lazy_initializer","handler","fieldHandler"})
public class WechatAccount {
    
    @Id
    @GeneratedValue
    private Long id;
    
    private String source;
    
    /** 相当于关注时间或浏览时间 */
    private Date createTime;
    
    /** 腾讯字段: 用户的标识，对当前公众号唯一 */
    private String openid;
    
    /** 腾讯字段: 用户的昵称 */
    private String nickname;
    
    /** 腾讯字段: 用户的性别，值为1时是男性，值为2时是女性，值为0时是未知 */
    private Integer sex;
    
    /** 腾讯字段: 用户所在省份 */
    private String province;
    
    /** 腾讯字段: 用户所在城市 */
    private String city;
    
    /** 腾讯字段: 用户所在国家 */
    private String country;
    
    /** 腾讯字段: 用户头像，最后一个数值代表正方形头像大小（有0、46、64、96、132数值可选，0代表640*640正方形头像），用户没有头像时该项为空。若用户更换头像，原有头像URL将失效。 */
    private String headimgurl;
    
    /** 腾讯字段: 只有在用户将公众号绑定到微信开放平台帐号后，才会出现该字段。 */
    private String unionid;
    
    /** 腾讯字段: 用户的语言，简体中文为zh_CN */
    private String language;
    
    /**腾讯字段: 用户关注时间，为时间戳。如果用户曾多次关注，则取最后关注时间 */
    private Long subscribeTime;
    
    /** 腾讯字段: 公众号运营者对粉丝的备注，公众号运营者可在微信公众平台用户管理界面对粉丝添加备注 */
    private String remark;
    
    /** 腾讯字段: 用户所在的分组ID */
    private String groupid;
    
    /** 腾讯字段: 小程序用户登录session标识 */
    private String sessionKey;
    
    /**
     * Default constructor
     */
    public WechatAccount() {
        
    }
    
    /**
     * construct for WeApp
     * 
     * @param source
     * @param sessionKey
     * @param unionid
     * @param nickname
     * @param sex
     * @param country
     * @param province
     * @param headimgurl
     */
    public WechatAccount(String source, String sessionKey, String unionid, String nickname, Integer sex, String country, String province, String headimgurl) {
        this.sessionKey = sessionKey;
        this.source = source;
        this.unionid = unionid;
        this.nickname = nickname;
        this.sex = sex;
        this.country = country;
        this.province = province;
        this.headimgurl = headimgurl;
    }
    
    /**
     * 
     * @param newAccount
     * @return
     */
    public WechatAccount refresh(WechatAccount newAccount) {
        this.openid = newAccount.getOpenid();
        this.nickname = newAccount.getNickname();
        this.sex = newAccount.getSex();
        this.province = newAccount.getProvince();
        this.city = newAccount.getCity();
        this.country = newAccount.getCountry();
        this.headimgurl = newAccount.getHeadimgurl();
        this.unionid = newAccount.getUnionid();
        this.language = newAccount.getLanguage();
        this.subscribeTime = newAccount.getSubscribeTime();
        this.remark = newAccount.getRemark();
        this.groupid = newAccount.getGroupid();
        
        return this;
    }
    
    /**
     * 
     * @param sessionKey
     * @param nickname
     * @param sex
     * @param country
     * @param province
     * @param headimgurl
     * @return
     */
    public WechatAccount refresh(String sessionKey, String nickname, Integer sex, String country, String province, String headimgurl) {
        this.sessionKey = sessionKey;
        this.nickname = nickname;
        this.sex = sex;
        this.country = country;
        this.province = province;
        this.headimgurl = headimgurl;
        return this;
    }
    
    /**
     * 
     * @param data
     * @param source
     */
    public WechatAccount(Map<String, Object> data, String source) {
        this.source = source;
        this.openid = data.containsKey("openid") ? data.get("openid").toString() : null;
        this.nickname = data.containsKey("nickname") ? data.get("nickname").toString() : null;
        this.sex = data.containsKey("sex") ? Integer.valueOf(data.get("sex").toString()) : 0;
        this.province = data.containsKey("province") ? data.get("province").toString() : null;
        this.city = data.containsKey("city") ? data.get("city").toString() : null;
        this.country = data.containsKey("country") ? data.get("country").toString() : null;
        this.headimgurl = data.containsKey("headimgurl") ? data.get("headimgurl").toString() : null;
        this.unionid = data.containsKey("unionid") ? data.get("unionid").toString() : null;
        this.language = data.containsKey("language") ? data.get("language").toString() : null;
        this.subscribeTime = data.containsKey("subscribe_time") ? Long.valueOf(data.get("subscribe_time").toString()): null;
        this.remark = data.containsKey("remark") ? data.get("remark").toString() : null;
        this.groupid = data.containsKey("groupid") ? data.get("groupid").toString() : null;
    }
    
    /**
     * 
     * @param source
     * @return
     */
    public WechatAccount bindSource(String source) {
      this.source = source;
      return this;
    }
    
    /**
     * construct map for WeChat
     * 
     * @return
     */
    public Map<String, Object> describeForWechat() {
        Map<String, Object> data = new LinkedHashMap<String, Object>();
        data.put("openid", this.openid);
        data.put("unionid", this.unionid);
        data.put("avator", this.headimgurl);
        data.put("nickname", this.nickname);
        data.put("sex", this.sex);
        return data;
    }

    /**
     * 
     * @param id
     * @return
     */
    public WechatAccount primary(Long id) {
        this.id = id;
        return this;
    }

    
    /**
     * @param data
     */
    public WechatAccount(Map<String, Object> data) {
        data(data);
    }

    /**
     * 
     * @param data
     * @return
     */
    public WechatAccount data(Map<String, Object> data) {
        
        this.openid = data.containsKey("openid") ? data.get("openid").toString() : null;
        this.nickname = data.containsKey("nickname") ? data.get("nickname").toString() : null;
        this.sex = data.containsKey("sex") ? Integer.valueOf(data.get("sex").toString()) : 0;
        this.province = data.containsKey("province") ? data.get("province").toString() : null;
        this.city = data.containsKey("city") ? data.get("city").toString() : null;
        this.country = data.containsKey("country") ? data.get("country").toString() : null;
        this.headimgurl = data.containsKey("headimgurl") ? data.get("headimgurl").toString() : null;
        this.unionid = data.containsKey("unionid") ? data.get("unionid").toString() : null;
        this.language = data.containsKey("language") ? data.get("language").toString() : null;
        this.subscribeTime = data.containsKey("subscribe_time") ? Long.valueOf(data.get("subscribe_time").toString()): null;
        this.remark = data.containsKey("remark") ? data.get("remark").toString() : null;
        this.groupid = data.containsKey("groupid") ? data.get("groupid").toString() : null;
        
        return this;
    }
    
    /**
     * Get Sex enum
     * 
     * @return
     */
    @Transient
    public Gender getSexEnum() {
        return Gender.codeOf(this.getSex());
    }
    
    /**
     * 
     * @return
     */
    @Transient
    public Date getSubscribeTimeAsDate() {
        if(this.subscribeTime != null) {
            return new Date(this.subscribeTime);
        }
        return null;
    }

    public Long getId() {
      return id;
    }

    public void setId(Long id) {
      this.id = id;
    }

    public String getSource() {
      return source;
    }

    public void setSource(String source) {
      this.source = source;
    }

    public Date getCreateTime() {
      return createTime;
    }

    public void setCreateTime(Date createTime) {
      this.createTime = createTime;
    }

    public String getOpenid() {
      return openid;
    }

    public void setOpenid(String openid) {
      this.openid = openid;
    }

    public String getNickname() {
      return nickname;
    }

    public void setNickname(String nickname) {
      this.nickname = nickname;
    }

    public Integer getSex() {
      return sex;
    }

    public void setSex(Integer sex) {
      this.sex = sex;
    }

    public String getProvince() {
      return province;
    }

    public void setProvince(String province) {
      this.province = province;
    }

    public String getCity() {
      return city;
    }

    public void setCity(String city) {
      this.city = city;
    }

    public String getCountry() {
      return country;
    }

    public void setCountry(String country) {
      this.country = country;
    }

    public String getHeadimgurl() {
      return headimgurl;
    }

    public void setHeadimgurl(String headimgurl) {
      this.headimgurl = headimgurl;
    }

    public String getUnionid() {
      return unionid;
    }

    public void setUnionid(String unionid) {
      this.unionid = unionid;
    }

    public String getLanguage() {
      return language;
    }

    public void setLanguage(String language) {
      this.language = language;
    }

    public Long getSubscribeTime() {
      return subscribeTime;
    }

    public void setSubscribeTime(Long subscribeTime) {
      this.subscribeTime = subscribeTime;
    }

    public String getRemark() {
      return remark;
    }

    public void setRemark(String remark) {
      this.remark = remark;
    }

    public String getGroupid() {
      return groupid;
    }

    public void setGroupid(String groupid) {
      this.groupid = groupid;
    }

    public String getSessionKey() {
      return sessionKey;
    }

    public void setSessionKey(String sessionKey) {
      this.sessionKey = sessionKey;
    }
}
